//-----------------------------------------------------
// Design Name : 
// File Name : 
// Function : 
//-----------------------------------------------------
module ALU #(parameter WIDTH = 16)
            (input      [WIDTH-1:0] a, b, 
             input      [2:0]       alucont, 
             output reg [WIDTH-1:0] result,
				 output reg [WIDTH-1:0] flag
				 );

   wire     [WIDTH:0] b2, sum;
	reg C, L, F, Z, N;
	
	
   assign b2 = alucont[2] ? ~b:b;
   assign sum = a + b2 + alucont[2];
   // slt should be 1 if most significant bit of sum is 1
   

   always@(*)
      case(alucont[1:0])
         2'b00: result <= a & b;
         2'b01: result <= a | b;
         2'b10: result <= sum;
         2'b11: result <= a ^ b;
			default:
			result <= a & b;
      endcase
	always@(*)
	begin
		C <= sum[WIDTH];
		
		if(a<b)
		L <= 1;
		else
		L <= 0;
		
		
		F <= (~(a[WIDTH-1]) & ~(b[WIDTH-1]) & (sum[WIDTH-1])) | ((a[WIDTH-1]) & (b[WIDTH-1]) & ~(sum[WIDTH-1]));
		
		if(a == b)
		Z <= 1;
		else
		Z <= 0;
		
		if(a[WIDTH-1]>b[WIDTH-1])
		N <= 1;
		else if(a[WIDTH-1] < b[WIDTH-1])
		N <= 0;
		else
		begin
		if(a < b)
		N <= 1;
		else 
		N <= 0;
		end
	end
	
	
	always@(*)
	begin
		flag[7] <= 0;
		flag[11] <= 0;
		flag[12] <= 0;
		flag[13] <= L;     //rrrrIPE0NZF00LTC,
		flag[10] <= F;
		flag[9] <= Z;
		flag[8] <= N;
		flag[15] <= C;		
	end
endmodule
